package com.sofwin.service.impl;

import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.sofwin.mapper.SysResourceMapper;
import com.sofwin.mapper.SysRoleMapper;
import com.sofwin.mapper.SysRoleResourceMapper;
import com.sofwin.pojo.*;
import com.sofwin.service.RoleService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;
@Service
public class RoleServiceImpl implements RoleService {
    @Autowired
    private SysRoleMapper mapper;
    @Autowired
    private SysRoleResourceMapper roleResourceMapper;
    @Autowired
    private SysResourceMapper resourceMapper;
    @Override
    public List<SysRole> selectAllRoles() {
        return mapper.selectByExample(null);
    }

    @Override
    public PageInfo<SysRole> selectByPage(SysRole role, Integer pageNumber, Integer pageSize) {

        SysRoleExample example = new SysRoleExample();
        SysRoleExample.Criteria criteria = example.createCriteria();
        if(role!=null){
            if(role.getRoleName()!=null && !"".equals(role.getRoleName())){
                criteria.andRoleNameLike("%"+role.getRoleName()+"%");
            }
            if(role.getFlag()!=null && role.getFlag()!=0){
                criteria.andFlagEqualTo(role.getFlag());
            }
        }
        PageHelper.startPage(pageNumber,pageSize);
        List<SysRole> roles = mapper.selectByExample(example);
        return new PageInfo<SysRole>(roles);
    }

    @Override
    public SysRole selectById(Integer id) {
        return mapper.selectByPrimaryKey(id);
    }

    @Override
    public boolean saveRole(SysRole role) {
        if(role.getId()!=null && role.getId()!=0){
            return mapper.updateByPrimaryKeySelective(role)==1?true:false;
        }
        return mapper.insertSelective(role)==1?true:false;
    }

    @Override
    public boolean deleteByIds(Integer[] ids) {
        int flag=0;
        for(Integer id:ids){
           flag+= mapper.deleteByPrimaryKey(id);
        }
        return flag==ids.length?true:false;
    }

    @Override
    public boolean savePermission(Integer roleId, Integer resourceId, Integer flag) {
        boolean status = false;
        SysResource currentResource = resourceMapper.selectByPrimaryKey(resourceId);
        if(flag==0){
            // 取消权限
            // 判断当前资源是否为父资源
            if(isParentResource(resourceId)){
                status = deleteParentAndChildren(roleId,resourceId);
            }else{
                if(isLastChild(resourceId,roleId)){
                    // 判断是否为最后一个子节点
                    status =   deleteParentAndChildren(roleId,currentResource.getParentId());
                }else {
                    status =  deleteResourceById(resourceId,roleId);
                }
            }
        }else{
            // 添加权限
            if(isParentResource(resourceId)){
                status =  saveParentAndChildren(roleId,resourceId);
            }else {
                if(isFirstChild(resourceId,roleId)){
                    // 保存的弟一个节点，先保存父节点
                    status =  saveRoleResource(currentResource.getParentId(),roleId);
                }
                status = saveRoleResource(currentResource.getId(),roleId);
            }
        }
        return status;
    }

    @Override
    public boolean savePermissions(Integer roleId, Integer[] resourceIds) {
       boolean status = false;
       int flag=0;
       if(resourceIds!=null && resourceIds.length>0){
           // 将当前角色的所有权限先删除掉
           SysRoleResourceExample example = new SysRoleResourceExample();
           SysRoleResourceExample.Criteria criteria = example.createCriteria();
           criteria.andRoleIdEqualTo(roleId);
           roleResourceMapper.deleteByExample(example);
           // 再循环插入
           for (Integer resourceId:resourceIds) {
               SysRoleResource roleResource = new SysRoleResource();
               roleResource.setRoleId(roleId);
               roleResource.setResourceId(resourceId);
               flag+=roleResourceMapper.insertSelective(roleResource);
           }
       }
       if(resourceIds==null || resourceIds.length==0){
           status = true;
       }else if(flag==resourceIds.length){
           status = true;
       }
        return status;
    }

    private boolean saveRoleResource(Integer parentId, Integer roleId) {
        SysRoleResource roleResource = new SysRoleResource();
        roleResource.setResourceId(parentId);
        roleResource.setRoleId(roleId);
        int num = roleResourceMapper.insertSelective(roleResource);
        return num==1?true:false;
    }

    /**
     * 判断当前节点是否为第一个子节点
     * @param resourceId  节点id
     * @param roleId 角色id
     * @return
     */
    private boolean isFirstChild(Integer resourceId, Integer roleId) {
        SysResource parent = resourceMapper.selectByPrimaryKey(resourceId);
        SysRoleResourceExample example2 = new SysRoleResourceExample();
        SysRoleResourceExample.Criteria criteria1 = example2.createCriteria();
        criteria1.andRoleIdEqualTo(roleId);
        criteria1.andResourceIdEqualTo(parent.getParentId());
        long num = roleResourceMapper.countByExample(example2);
        return num==0?true:false;
    }

    /**
     * 保存父+子
     * @param roleId
     * @param resourceId
     */
    private boolean saveParentAndChildren(Integer roleId, Integer resourceId) {
        int num = roleResourceMapper.saveParentAndChildren(roleId,resourceId);
        // resourceId获取子节点的id 集合
        // 循环插入
        return num>0?true:false;
    }

    /**
     * 删除当前权限
     * @param resourceId
     * @param roleId
     */
    private boolean deleteResourceById(Integer resourceId, Integer roleId) {
        SysRoleResourceExample example = new SysRoleResourceExample();
        SysRoleResourceExample.Criteria criteria = example.createCriteria();
        criteria.andResourceIdEqualTo(resourceId);
        criteria.andRoleIdEqualTo(roleId);
        int i = roleResourceMapper.deleteByExample(example);
        return i>0?true:false;
    }

    /**
     * 判断当前节点是否为最后一个子节点
     * @param resourceId
     * @param roleId
     * @return
     */
    private boolean isLastChild(Integer resourceId, Integer roleId) {
        Integer num = roleResourceMapper.selectResourceIsLast(roleId,resourceId);
        return num==1?true:false;
    }

    /**
     * 删除父+子节点
     * @param roleId
     * @param resourceId
     */
    private boolean deleteParentAndChildren(Integer roleId, Integer resourceId) {
      int num =  roleResourceMapper.deleteParentAndChildren(roleId,resourceId);
      return num>0?true:false;
    }

    /**
     * 判断当前节点是否为父节点
     * @param resourceId
     * @return
     */
    private boolean isParentResource(Integer resourceId) {
        SysResource resource = resourceMapper.selectByPrimaryKey(resourceId);
        return resource.getParentId()==0?true:false;
    }

}
